---
menu: Guides
title: Babel plugin
order: 70
---

# Babel plugin

This plugin adds support for [Server Side Rendering](/docs/server-side-rendering) and automatic chunk names.

## Usage

Install the babel plugin first:

```bash
npm install --save-dev @loadable/babel-plugin
```

Then add it to your babel configuration like so:

```json
{
  "plugins": ["@loadable/babel-plugin"]
}
```

## Transformation

The plugin transforms your code to be ready for Server Side Rendering, it turns a loadable call:

```js
import loadable from '@loadable/component'

const OtherComponent = loadable(() => import('./OtherComponent'))
```

into another one with some informations required for Server Side Rendering:

```js
import loadable from '@loadable/component'
const OtherComponent = loadable({
  chunkName() {
    return 'OtherComponent'
  },

  isReady(props) {
    if (typeof __webpack_modules__ !== 'undefined') {
      return !!__webpack_modules__[this.resolve(props)]
    }

    return false
  },

  requireAsync: () =>
    import(/* webpackChunkName: "OtherComponent" */
    './OtherComponent'),

  requireSync(props) {
    const id = this.resolve(props)

    if (typeof __webpack_require__ !== 'undefined') {
      return __webpack_require__(id)
    }

    return eval('module.require')(id)
  },

  resolve() {
    if (require.resolveWeak) {
      return require.resolveWeak('./OtherComponent')
    }

    return require('path').resolve(__dirname, './OtherComponent')
  },
})
```

As you can see the "webpackChunkName" annotation is automatically added.

On client side, the two code are completely compatible.

Please note that babel must not be configured [to strip comments](https://babeljs.io/docs/en/options#comments), since the chunk name is defined in a comment.

## Loadable Configuration (beta)
> available since 5.16.0

Sometimes you need to wrap loadable with your own custom logic. There are many use cases for it, from injecting telemetry to hiding external libraries behind facade.
By default `loadable-components` are configured to transform dynamic imports used only inside loadable helpers, but can be configured to instrument any other function of your choice.
```json
{
  "plugins": ["@loadable/babel-plugin", {
     "signatures": [
        { "name": "default", "from": "myLoadableWrapper" }
        { "name": "myLoadableHelper", "from": "myLoadableWrapper" }
     ]
  }]
}
```
```tsx
import {myLoadableHelper} from "myLoadableWrapper";
const Loadable = myLoadableHelper(() => import("./MyComponent"));
// will behave similar to
import loadable from '@loadable/component'
const OtherComponent = loadable(() => import('./OtherComponent'))
```

## Loadable detection (deprecated)
> Please dont use this feature and prefer Loadable Configuration instead

The detection of a loadable component is based on the keyword "loadable". It is an opinionated choice, it gives you flexibility but it could also be restrictive.

This code will not be transformed by the babel plugin:

```js
import load from '@loadable/component'
const OtherComponent = load(() => import('./OtherComponent'))
```

The `load` function is not detected, you have to name it `loadable`.

It is restrictive, yes but it could gives you some flexibility. You can create your own loadable function. In the following example we create a custom loadable function with a custom fallback:

```js
import baseLoadable from '@loadable/component'

function loadable(func) {
  return baseLoadable(func, { fallback: <div>Loading...</div> })
}

const OtherComponent = loadable(() => import('./OtherComponent'))
```

## Magic comments

To gives you flexibility and portability, the babel plugin supports magic comment. This way you can create portable "load" functions. To create a "load" function, you have to add `/* #__LOADABLE__ */` comment above the declaration of your function (variable or property):

```js
const loadOther = /* #__LOADABLE__ */ () => import('./OtherComponent')

const OtherComponent = loadable(loadOther)
```

The `loadOther` function will be transformed into an object, this way you can manipulate function and it is still portable!
